package algotithm.juc.test1115;

import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

/**
 * @author zhouyanxiang
 * @Date 2021-04-2021/4/9-15:56
 * @Title 1115. 交替打印FooBar
 */
class FooBar {

    public static void main(String[] args) {
        FooBar f = new FooBar(20);
        new Thread(new Runnable() {
            @Override
            public void run() {

            }
        }).start();

        new Thread(new Runnable() {
            @Override
            public void run() {

            }
        }).start();
    }

    private int n;
    Lock lock = new ReentrantLock();
    Condition A = lock.newCondition();
    Condition B = lock.newCondition();
    volatile int state = 0;
    public FooBar(int n) {
        this.n = n;
    }

    public void foo(Runnable printFoo) throws InterruptedException {
        for (int i = 0; i < n; i++) {
            lock.lock();
            try {
                while(state!=0) {
                    A.await();
                }
                // printFoo.run() outputs "foo". Do not change or remove this line.
                printFoo.run();
                System.out.println("Foo");
                state = 1;
                B.signal();
            } catch (Exception e) {
                e.printStackTrace();
            } finally {
                lock.unlock();
            }
        }
    }

    public void bar(Runnable printBar) throws InterruptedException {
        for (int i = 0; i < n; i++) {
            lock.lock();
            try {
                while(state!=1) {
                    B.await();
                }
                // printBar.run() outputs "bar". Do not change or remove this line.
                printBar.run();
                state = 0;
                A.signal();
            } finally {
                lock.unlock();
            }

        }
    }
}
